home *** CD-ROM | disk | FTP | other *** search
/ Atari Mega Archive 1 / Atari Mega Archive - Volume 1.iso / telecomm / zmdm_src.arc / SZ.C < prev    next >
C/C++ Source or Header  |  1988-06-26  |  30KB  |  1,548 lines

  1. /*
  2.  *                ACKNOWLEDGEMENTS
  3.  *
  4.  *    ZMDM was derived from rz/sz for Unix  posted by 
  5.  *    Chuck Forsberg (...!tektronix!reed!omen!caf ). We
  6.  *    thank him for his excellent code, and for giving
  7.  *    us permission to use and distribute his code and
  8.  *    documentation.
  9.  *
  10.  *    Atari St version by:
  11.  *        Jwahar Bammi
  12.  *            usenet: mandrill!bammi@{decvax,sun}.UUCP
  13.  *            csnet:  bammi@mandrill.ces.CWRU.edu
  14.  *            arpa:   bammi@mandrill.ces.CWRU.edu
  15.  *            CompuServe: 71515,155
  16.  */
  17.  
  18. #include "config.h"
  19. #define SVERSION "sz 1.23 01-15-87"
  20. #define SSTVERSION "sz 1.01 03-07-87"
  21. #define OS    "Unix V7/BSD"
  22.  
  23. #ifndef STANDALONE
  24. #define RETURN return
  25. #else
  26. int bibi() {} /* dummy */
  27. #endif 
  28.  
  29. /* #define SDEBUG */
  30.  
  31. /*
  32.  * sz.c By Chuck Forsberg
  33.  *
  34.  *    cc -O sz.c -o sz        USG (SYS III/V) Unix
  35.  *     cc -O -DV7  sz.c -o sz        Unix Version 7, 2.8 - 4.3 BSD
  36.  *
  37.  *        define CRCTABLE to use table driven CRC
  38.  *
  39.  *  ******* Some systems (Venix, Coherent, Regulus) do not *******
  40.  *  ******* support tty raw mode read(2) identically to    *******
  41.  *  ******* Unix. ONEREAD must be defined to force one     *******
  42.  *  ******* character reads for these systems.           *******
  43.  *
  44.  * A program for Unix to send files and commands to computers running
  45.  *  Professional-YAM, PowerCom, YAM, IMP, or programs supporting Y/XMODEM.
  46.  *
  47.  *  Sz uses buffered I/O to greatly reduce CPU time compared to UMODEM.
  48.  *
  49.  *  USG UNIX (3.0) ioctl conventions courtesy Jeff Martin
  50.  *
  51.  *    St v 1.01
  52.  *        added support for 32 bit CRC's (Zmodem) ++jrb
  53.  *
  54.  */
  55.  
  56. #include "zmdm.h"
  57. #include "common.h"
  58. #include "zmodem.h"
  59.  
  60. #ifndef Vsync             /* Atari forgot these in osbind.h */
  61. #define Vsync()    xbios(37)
  62. #endif
  63.  
  64. #ifndef Supexec
  65.         /* Some versions of osbind don't define Supexec */
  66. #define Supexec(X) xbios(38,X)
  67. #endif
  68.  
  69. #define SLOGFILE "szlog"
  70.  
  71. #define purgeline()    while(Bconstat(1)) Bconin(1)
  72. #define S_IFDIR 0x0010
  73.  
  74. /*
  75.  * Attention string to be executed by receiver to interrupt streaming data
  76.  *  when an error is detected.  A pause (0336) may be needed before the
  77.  *  ^C (03) or after it.
  78.  */
  79. #ifdef READCHECK
  80. char Myattn[] = { 0 };
  81. #else
  82. #ifdef USG
  83. char Myattn[] = { 03, 0336, 0 };
  84. #else
  85. char Myattn[] = { 0 };
  86. #endif
  87. #endif
  88.  
  89. #if (MWC || MANX)
  90. FILE *fopen();
  91. #else
  92. FILE *fopen(), *fopenb();
  93. #endif
  94. static unsigned long SaveIntr;
  95. static int Resuming, ForceBin;
  96. static int in;
  97.  
  98. /* called by signal interrupt or terminate to clean things up */
  99. bibis(n)
  100. int n;
  101. {
  102.     canit(); flush_modem(); mode(0);
  103.     fprintf(STDERR, "\r\nsz: caught signal %d; exiting\n", n);
  104.  
  105.     aexit(128+n);
  106. }
  107.  
  108. /* Called when Zmodem gets an interrupt (^X) */
  109. #ifdef ONINTR
  110. onintr()
  111. {
  112.     siggi = 0;
  113.     longjmp(intrjmp, -1);
  114. }
  115. #endif
  116.  
  117. #define ZKER
  118. int Zctlesc;    /* Encode control characters */
  119.  
  120. #ifdef STANDALONE
  121. int main(argc, argv)
  122. #else
  123. int dosz(argc, argv)
  124. #endif
  125. int argc;
  126. char **argv;
  127. {
  128.     register char *cp;
  129.     register int npats;
  130.     int agcnt; char **agcv;
  131.     char **patts;
  132.  
  133. #ifdef STANDALONE
  134. #ifdef MWC
  135.     extern char *lmalloc();
  136. #endif
  137.  
  138.     /* Set up Dta */
  139.     Fsetdta(&statbuf);
  140.  
  141.     /* Get screen rez */
  142.     rez = Getrez();
  143.     drv_map = Drvmap();
  144.  
  145. #if (MWC || MANX)
  146. #ifndef DYNABUF
  147. #ifdef MWC
  148.     if((bufr = (unsigned char *)lmalloc((unsigned long)BBUFSIZ))
  149.                      == (unsigned char *)NULL)
  150. #else
  151.     if((bufr = (unsigned char *)Malloc((unsigned long)BBUFSIZ))
  152.                      == (unsigned char *)NULL)
  153. #endif
  154. #else
  155.     if((bufr = dalloc()) == (unsigned char *)NULL)
  156. #endif /* DYNABUF */
  157.     {
  158. #ifdef REMOTE
  159.         Bauxws("Sorry, could not allocate enough memory\r\n");
  160. #else
  161.         Bconws("Sorry, could not allocate enough memory\r\n");
  162. #endif
  163.  
  164.         Pterm(4);
  165.     }
  166. #else /* MWC || MANX */
  167. #ifdef DYNABUF
  168.     if((bufr = dalloc()) == (unsigned char *)NULL)
  169.     {
  170. #ifdef REMOTE
  171.         Bauxws("Sorry, could not allocate enough memory\r\n");
  172. #else
  173.         Bconws("Sorry, could not allocate enough memory\r\n");
  174. #endif
  175.         Pterm(5);
  176.     }
  177. #endif /* DYNABUF */
  178. #endif /* MWC || MANX */
  179.  
  180. #ifndef REMOTE
  181.     STDERR = stderr;
  182. #else
  183. #ifndef DLIBS
  184.     if((STDERR = fopen("aux:", "rw")) == (FILE *)NULL)
  185.     {
  186.         Bauxws("Could not Open Aux Stream for Stderr\r\n");
  187.         finish();
  188.     }
  189.     setbuf(STDERR, (char *)NULL);
  190. #else
  191.     STDERR = stdaux;
  192. #endif /* DLIBS */
  193.     
  194. #endif /* REMOTE */
  195.     {
  196.         int speed;
  197.         speed = getbaud();
  198.         Baudrate = BAUD_RATE(speed);
  199.         SetIoBuf();
  200.         Rsconf(speed, 0,-1,-1,-1,-1);
  201.         Vsync(); Vsync();
  202.     }
  203. #endif /* STANDALONE */
  204.  
  205.     SendType = 1;
  206.     Rxtimeout = 600;
  207.     npats=0;
  208.     if (argc<2)
  209.     {
  210.         susage();
  211.         RETURN(1);
  212.     }
  213.  
  214.     initz();
  215. #ifndef STANDALONE
  216.     schkinvok(argv[0]);
  217. #else
  218.     Progname = "sz";
  219. #endif
  220.  
  221.     SaveIntr = Setexc(0x0102, -1L);
  222.     BusErr   = Setexc(2, -1L);
  223.     AddrErr  = Setexc(3, -1L);
  224.  
  225.     Verbose = 0;
  226.     Resuming = FALSE;
  227.     ForceBin = FALSE;
  228.     in = (-1);
  229.     vdebug = 0;
  230.  
  231. #ifdef SDEBUG
  232.     logf = (FILE *)NULL;
  233. #endif
  234.     while (--argc) {
  235.         cp = *++argv;
  236.         if (*cp++ == '-' && *cp) {
  237.             while ( *cp) {
  238.                 switch(*cp++) {
  239.                 case '+':
  240.                     Lzmanag = ZMAPND; break;
  241. #ifdef CSTOPB
  242.                 case '2':
  243.                     Twostop = TRUE; break;
  244. #endif
  245.                 case '7':
  246.                     Wcsmask=0177; break;
  247.  
  248. /*
  249.     On the St we look up the ext and decide. For Xmodem
  250.     transfers, the file is always sent in binary mode
  251.     and it is the responsibility of the receiver to
  252.     strip CR if so desired.
  253.                 case 'a':
  254.                     Lzconv = ZCNL;
  255.                     Ascii = TRUE; break;
  256.                 case 'b':
  257.                     Lzconv = ZCBIN; break;
  258. */
  259.  
  260. /*  ST extention, force binary, useful to back up every thing
  261.  *  in image mode, see -B option of rz too +jrb
  262.  */
  263.                 case 'B':
  264.                     ForceBin = TRUE;
  265.                     Lzconv = ZCBIN;
  266.                     break;
  267.                 case 'C':
  268.                     if (--argc < 1) {
  269.                         susage();
  270.                         RETURN(1);
  271.                     }
  272.                     Cmdtries = atoi(*++argv);
  273.                     break;
  274.                 case 'i':
  275.                     Cmdack1 = ZCACK1;
  276.                     /* **** FALL THROUGH TO **** */
  277.                 case 'c':
  278.                     if (--argc != 1) {
  279.                         susage();
  280.                         RETURN(1);
  281.                     }
  282.                     Command = TRUE;
  283.                     Cmdstr = *++argv;
  284.                     break;
  285.                 case 'd':
  286.                     ++Dottoslash;
  287.                     /* **** FALL THROUGH TO **** */
  288.                 case 'f':
  289.                     Fullname=TRUE; break;
  290.                 case 'E':
  291.                     Zctlesc = (-1); break;
  292.                 case 'e':
  293.                     Zctlesc = 1; break;
  294.                 case 'k':
  295.                     Blklen=KSIZE; break;
  296.                 case 'L':
  297.                     if (--argc < 1) {
  298.                         susage();
  299.                         RETURN(1);
  300.                     }
  301.                     blkopt = atoi(*++argv);
  302.                     if (blkopt<32 || blkopt>1024)
  303.                     {
  304.                         susage();
  305.                         RETURN(1);
  306.                     }
  307.                     break;
  308.                 case 'l':
  309.                     if (--argc < 1) {
  310.                         susage();
  311.                         RETURN(1);
  312.                     }
  313.                     Tframlen = atoi(*++argv);
  314.                     if (Tframlen<32 || Tframlen>1024)
  315.                     {
  316.                         susage();
  317.                         RETURN(1);
  318.                     }
  319.                     break;
  320.                 case 'N':
  321.                     Lzmanag = ZMDIFF;  break;
  322.                 case 'n':
  323.                     Lzmanag = ZMNEW;  break;
  324.                 case 'o':
  325.                     Wantfcs32 = FALSE; break;
  326.                 case 'p':
  327.                     Lzmanag = ZMPROT;  break;
  328.                 case 'r':
  329.                     Lzconv = ZCRESUM; Resuming = TRUE; break;
  330.                 case 'q':
  331.                     Quiet=TRUE; Verbose=0; break;
  332.                 case 't':
  333.                     if (--argc < 1) {
  334.                         susage();
  335.                         RETURN(1);
  336.                     }
  337.                     Rxtimeout = atoi(*++argv);
  338.                     if (Rxtimeout<10 || Rxtimeout>1000)
  339.                     {
  340.                         susage();
  341.                         RETURN(1);
  342.                     }
  343.                     break;
  344. #ifdef TESTATTN
  345.                 case 'T':
  346.                     Testattn = TRUE; break;
  347. #endif
  348.                 case 'u':
  349.                     ++Unlinkafter; break;
  350.                 case 'v':
  351.                     ++Verbose; break;
  352.                 case 'X':
  353.                     ++Modem; break;
  354.                 case 'y':
  355.                     Lzmanag = ZMCLOB; break;
  356.                 default:
  357.                     susage();
  358.                     RETURN(1);
  359.                 }
  360.             }
  361.         }
  362.         else if ( !npats && argc>0) {
  363.             if (argv[0][0]) {
  364.                 npats=argc;
  365.                 patts=argv;
  366.             }
  367.         }
  368.     }
  369.     if (npats < 1 && !Command) 
  370.     {
  371.         susage();
  372.         RETURN(1);
  373.     }
  374.  
  375. #ifdef SDEBUG
  376.     if (Verbose > 2)
  377.     {
  378.         if ((logf = fopen(SLOGFILE, "a"))== (FILE *)NULL)
  379.         {
  380.             fprintf(STDERR, "Can't open log file %s\n",SLOGFILE);
  381.             RETURN(0200);
  382.         }
  383.         fprintf(logf, "Progname=%s\n", Progname);
  384.         vdebug = 1;
  385.         fflush(logf);
  386.     }
  387. #endif
  388.  
  389.     if ( !Quiet)
  390.     {
  391.         if (Verbose < 2)
  392.             Verbose = 2;
  393.     }
  394.  
  395.  
  396.     Setexc(0x0102, bibis);
  397.     Setexc(2, buserr);
  398.     Setexc(3, addrerr);
  399.  
  400.     if(setjmp(busjmp))
  401.     {
  402.         /* On a bus error - instead of 2 bombs */
  403.         fprintf(STDERR,"\r\nFATAL: Bus Error\n\n");
  404. #ifdef SDEBUG
  405.         if(logf != (FILE *)NULL)
  406.             fclose(logf);
  407. #endif
  408.         if(in != -1)
  409.         {
  410.             stfclose(in);
  411.             in = (-1);
  412.         }
  413.         canit();
  414.         Setexc(2, BusErr);
  415.         Setexc(3, AddrErr);
  416.         Setexc(0x0102, SaveIntr);
  417.         RETURN(2);
  418.     }
  419.  
  420.     if(setjmp(addrjmp))
  421.     {
  422.         /* On address error - instead of 3 bombs */
  423.         fprintf(STDERR,"\r\nFATAL: Address Error\n\n");
  424. #ifdef SDEBUG
  425.         if(logf != (FILE *)NULL)
  426.             fclose(logf);
  427. #endif
  428.         if(in != -1)
  429.         {
  430.             stfclose(in);
  431.             in = (-1);
  432.         }
  433.         canit();
  434.         S